package com.spzx.common.security.aspect;

import com.alibaba.fastjson2.JSON;
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import com.spzx.common.security.annotation.SpzxPrintLog;
import jakarta.servlet.http.HttpServletRequest;
import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.stereotype.Component;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import java.util.Map;


@Slf4j
@Aspect
@Component
public class SpzxPrintLogAspect {
    //@Around(value = "execution()")   //环绕通知  使用全类名+方法+形参列表  作为切入点
    //@Around(value = "@annotation(com.spzx.common.security.annotation.SpzxPrintLog)") //环绕通知  使用注解作为切入点
    @Around(value = "@annotation(spzxPrintLog)")
    public Object printLog(ProceedingJoinPoint proceedingJoinPoint, SpzxPrintLog spzxPrintLog) {
        //1、目标方法执行前的逻辑
        try {
            long startTime = System.currentTimeMillis();
            String params = "";
            //获取请求参数
            if (spzxPrintLog.isPrintRequestData()) {
                ServletRequestAttributes servletRequestAttributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
                HttpServletRequest request = servletRequestAttributes.getRequest();

                Map<String, String[]> parameterMap = request.getParameterMap();
                if (!CollectionUtils.isEmpty(parameterMap)) {
                    params = JSON.toJSONString(parameterMap);
                }
            }
            //需要使用目标方法上注解对象的属性值
            //2、执行目标方法得到的结果
            String printResult="";
            Object result = proceedingJoinPoint.proceed();
            //3、目标方法执行后的逻辑
            if (spzxPrintLog.isPrintResult()) {
                printResult = JSON.toJSONString(result);
            }
            log.info(spzxPrintLog.module()+"模板被访问了，参数：{} , 结果：{} , 执行时间：{}"
                    , params, printResult, (System.currentTimeMillis() - startTime)*1.0/1000);
            //4、返回目标方法执行+处理后的结果
            return result;
        } catch (Throwable e) {
            throw new RuntimeException(e);
        }
    }
}
